package com.mit.web.util
{
	import com.mit.web.business.proxy.InventoryProxy;
	import com.mit.web.business.proxy.MaintenanceProxy;
	import com.mit.web.business.proxy.ManufactureProxy;
	import com.mit.web.business.proxy.PurchaseProxy;
	import com.mit.web.business.proxy.SaleProxy;
	import com.mit.web.business.remote.AsyncResponder;
	import com.mit.web.business.remote.IInvokeResponder;
	import com.mit.web.business.remote.SyncResponder;
	import com.mit.web.config.DisplayConfiguration;
	
	import mx.collections.ArrayCollection;
	import mx.logging.ILogger;
	import mx.rpc.events.ResultEvent;

	/**
	 * 工具类：缓存池<br/>
	 * 该工具类使用singleTon模式，使用者不需新建对象实例，而应该通过getInstance()方法获取实例<br/>
	 * By YU
	 * */
	public class CachePool
	{
		private static var me:CachePool;
		private var _logger:ILogger;

		private var productTypeCache:CacheableObject;
		private var productColorCache:CacheableObject;
		private var seasonCache:CacheableObject;
		private var supplierCache:CacheableObject;
		private var materialCategoryCache:CacheableObject;
		private var unitCache:CacheableObject;
		private var factoryCache:CacheableObject;
		private var customerCache:CacheableObject;
		private var warehouseCache:CacheableObject;
		//添加更多的缓存对象...
		
		public function CachePool()
		{			
			if(me != null)
				throw new Error("Only one instance of this class is allowed, use getInstance() insteadof the constructor.");
			_logger = LogUtil.getLogger(this);
		}
		
		public static function getInstance():CachePool{
			if(me == null)
				me = new CachePool();
			return me;
		}
		
		private function cacheExpired(cache:CacheableObject):Boolean{
			var cacheLastUpdatedTime:Number = cache.lastUpdatedTime;
			var now:Number = Number(new Date());
			var maxAvalidTime:Number = cacheLastUpdatedTime + DisplayConfiguration.getInstance().CACHE_LIFE_CYCLE;
			return (now > maxAvalidTime);
		}
		
		private function createSyncResponder(cacheable:CacheableObject):SyncResponder{
			var result:ResultEvent = ResultEvent.createEvent(cacheable.cachedObject);
			var resp:SyncResponder = new SyncResponder();
			resp.invokeResult(result);
			return resp;
		}
		
		
		public function refreshCache(event:ResultEvent, cache:CacheableObject):void{
			cache = new CacheableObject(event.result);
		}
		
		//对象池中的管理对象必须实现各自的远程调用方法
	
		public function getProductTypes():IInvokeResponder{
			if(productTypeCache == null || cacheExpired(productTypeCache)){
				//Refresh cache if 
				//1) cache not exists
				//2) its life cycle is over
				var aresp:IInvokeResponder = MaintenanceProxy.getInstance().getProductTypes();
				aresp.addResultListener(refreshCache, productTypeCache);
				return aresp;
			}else{
				//Else, use cache
				var resp:SyncResponder = createSyncResponder(productTypeCache);
				return resp;
			}
			
		}
		
		public function getProductColor():IInvokeResponder{
			if(productColorCache == null || cacheExpired(productColorCache)){
				var aresp:IInvokeResponder = MaintenanceProxy.getInstance().getProductColors();
				aresp.addResultListener(refreshCache, productColorCache);
				return aresp;
			}else{
				var resp:SyncResponder = createSyncResponder(productColorCache);
				return resp;
			}
		}

		public function getSeasons():IInvokeResponder{
			if(seasonCache == null || cacheExpired(seasonCache)){
				var aresp:IInvokeResponder = MaintenanceProxy.getInstance().getSeasons();
				aresp.addResultListener(refreshCache, seasonCache);
				return aresp;
			}else{
				var resp:SyncResponder = createSyncResponder(seasonCache);
				return resp;
			}
		}
		public function getSuppliers():IInvokeResponder{
			if(supplierCache == null || cacheExpired(supplierCache)){
				_logger.info("Refresh supplier cache")
				var aresp:IInvokeResponder = PurchaseProxy.getInstance().getSuppliers();
				aresp.addResultListener(refreshCache, supplierCache);
				return aresp;
			}else{
				_logger.debug("Use supplier cache");
				var resp:SyncResponder = createSyncResponder(supplierCache);
				return resp;
			}
		}
		public function getMaterialCategorys():IInvokeResponder{
			if(materialCategoryCache == null || cacheExpired(materialCategoryCache)){
				_logger.info("Refresh category cache")
				var aresp:IInvokeResponder = MaintenanceProxy.getInstance().getFabricCats();
				aresp.addResultListener(refreshCache, materialCategoryCache);
				return aresp;
			}else{
				_logger.debug("Use supplier cache");
				var resp:SyncResponder = createSyncResponder(materialCategoryCache);
				return resp;
			}
		}
		public function getUnits():IInvokeResponder{
			if(unitCache == null || cacheExpired(unitCache)){
				_logger.info("Refresh category cache")
				var aresp:IInvokeResponder = MaintenanceProxy.getInstance().getUnits();
				aresp.addResultListener(refreshCache, unitCache);
				return aresp;
			}else{
				_logger.debug("Use supplier cache");
				var resp:SyncResponder = createSyncResponder(unitCache);
				return resp;
			}
		}	
		public function getFactories():IInvokeResponder{
			if(factoryCache == null || cacheExpired(factoryCache)){
				_logger.info("Refresh category cache")
				var aresp:IInvokeResponder = ManufactureProxy.getInstance().getFactoryBasicInfo();
				aresp.addResultListener(refreshCache, factoryCache);
				return aresp;
			}else{
				_logger.debug("Use supplier cache");
				var resp:SyncResponder = createSyncResponder(factoryCache);
				return resp;
			}
		}
		public function getCustomers():IInvokeResponder{
			if(customerCache == null || cacheExpired(customerCache)){
				_logger.info("Refresh category cache")
				var aresp:IInvokeResponder = SaleProxy.getInstance().getCustomerBasicInfo();
				aresp.addResultListener(refreshCache, customerCache);
				return aresp;
			}else{
				_logger.debug("Use supplier cache");
				var resp:SyncResponder = createSyncResponder(customerCache);
				return resp;
			}
		}
		public function getWarehouses():IInvokeResponder{
			if(warehouseCache == null || cacheExpired(warehouseCache)){
				_logger.info("Refresh category cache")
				var aresp:IInvokeResponder = InventoryProxy.getInstance().getWarehouseBasicInfo();
				aresp.addResultListener(refreshCache, warehouseCache);
				return aresp;
			}else{
				_logger.debug("Use supplier cache");
				var resp:SyncResponder = createSyncResponder(warehouseCache);
				return resp;
			}
		}
	}
}